<template>
    <div ref="editorform" class="ace-editor">
    </div>
</template>

<script setup>
import { ref, onMounted, onBeforeUnmount } from "vue"
import ace from "ace-builds"
import "ace-builds/src-noconflict/mode-java"
import "ace-builds/src-noconflict/theme-eclipse"
import "ace-builds/src-noconflict/ext-language_tools";

// 定义 ace 编辑器的配置选项
const options = {
    theme: `ace/theme/eclipse`, // 编辑器主题为 eclipse
    mode: `ace/mode/java`,      // 编辑器模式为 Java
    maxLines: 20,               // 设置编辑器最大行数为 20
    minLines: 10,               // 设置编辑器最小行数为 10
    fontSize: 15,               // 设置字体大小为 15px
};

let editor = null; // 用来存储 Ace 编辑器实例
const emit = defineEmits(['update:value']); // 定义事件发射器，用于向父组件发送自定义事件
const editorform = ref(null);   // 拿到"ace-editor"编辑器容器元素的引用

// 在组件挂载完成后执行初始化操作
onMounted(() => {
    init();  // 调用初始化函数
});

// 在组件销毁前执行清理操作
onBeforeUnmount(() => {
    clean();  // 调用销毁函数
});

// 初始化编辑器
function init() {
    // 使用 ace 编辑器实例化编辑器，传入一个容器和配置项
    editor = ace.edit(editorform.value, options); // editorform 是容器元素，options 是配置选项

    // 设置编辑器的选项，启用基本的自动补全功能
    editor.setOptions({
        enableBasicAutocompletion: true,  // 启用基本的自动补全功能
    });

    // 监听编辑器的 session 对象上的 change 事件，当内容变化时触发回调函数
    editor.getSession().on('change', () => {
        // 当编辑器的内容发生变化时，触发自定义事件 'update:value'
        // 使用 emit 方法通知父组件，更新编辑器的内容
        emit('update:value', editor.getValue());  // editor.getValue() 获取当前编辑器的内容
    });
}

// 销毁编辑器实例
function clean() {
    if (editor) {
        editor.destroy();
        editor = null;
    }
}

// 设置编辑器内容的方法，供父组件或其他地方调用
function setAceCode(content) {
    if (editor) {
        editor.setValue(content);  // 设置编辑器的内容
    }
}

// 暴露方法给父组件或其他地方使用
defineExpose({ setAceCode })
</script>

<style lang="scss" scoped>
.ace-editor {
    margin: 10px 0 0 0;
    width: 90%;
}
</style>
